package heap

// jvms8 6.5.instanceof
// jvms8 6.5.checkcast
func (self *Class) isAssignableFrom(other *Class) bool {
    s, t := other, self

    if s == t {
        return true
    }

    if !s.IsArray() {
        if !s.IsInterface() {
            // s is class
            if !t.IsInterface() {
                // t is not interface
                return s.IsSubClassOf(t)
            } else {
                // t is interface
                return s.IsImplements(t)
            }
        } else {
            // s is interface
            if !t.IsInterface() {
                // t is not interface
                return t.isJlObject()
            } else {
                // t is interface
                return t.isSuperInterfaceOf(s)
            }
        }
    } else {
        // s is array
        if !t.IsArray() {
            if !t.IsInterface() {
                // t is class
                return t.isJlObject()
            } else {
                // t is interface
                return t.isJlCloneable() || t.isJioSerializable()
            }
        } else {
            // t is array
            sc := s.ComponentClass()
            tc := t.ComponentClass()
            return sc == tc || tc.isAssignableFrom(sc)
        }
    }

    return false
}

// self 继承了 c
func (self *Class) IsSubClassOf(other *Class) bool {
    for c := self.superClass; c != nil; c = c.superClass {
        if c == other {
            return true
        }
    }
    return false
}

// self 实现了接口 iface
func (self *Class) IsImplements(iface *Class) bool {
    for c := self; c != nil; c = c.superClass {
        for _, i := range c.interfaces {
            if i == iface || i.isSubInterfaceOf(iface) {
                return true
            }
        }
    }
    return false
}

// self 继承了接口 iface
func (self *Class) isSubInterfaceOf(iface *Class) bool {
    for _, superInterface := range self.interfaces {
        if superInterface == iface || superInterface.isSubInterfaceOf(iface) {
            return true
        }
    }
    return false
}

func (self *Class) IsSuperClassOf(other *Class) bool {
    return other.IsSubClassOf(self)
}

// iface 继承 self
func (self *Class) isSuperInterfaceOf(iface *Class) bool {
    return iface.isSubInterfaceOf(self)
}